package org.ohuyo.libra.server.dao.impl;

import java.sql.Connection;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

import javax.annotation.Resource;

import org.hibernate.HibernateException;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.jdbc.Work;
import org.ohuyo.commons.query.HibernateDaoSupportEx;
import org.ohuyo.libra.server.dao.LoginTicketDao;
import org.ohuyo.libra.server.model.table.LoginTicketRecord;
import org.springframework.orm.hibernate3.HibernateCallback;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Isolation;

/**
 * 
 * @author rabbit
 * 
 */
@Service("org.ohuyo.libra.server.loginTicketDao")
public class LoginTicketDaoImpl extends HibernateDaoSupportEx implements
		LoginTicketDao {
	@Override
	@Resource(name = "org.ohuyo.libra.server.sessionFactory")
	public void setSessionFactoryEx(SessionFactory sessionFactory) {
		super.setSessionFactoryEx(sessionFactory);
	}

	public void updateLoginTicketRecord(LoginTicketRecord lr) {
		this.getHibernateTemplate().update(lr);
	}

	public void saveLoginTicketRecord(LoginTicketRecord lr) {
		this.getHibernateTemplate().save(lr);
	}

	public LoginTicketRecord getLoginRecord(long loginSeq) {
		return (LoginTicketRecord) this.getHibernateTemplate().get(
				LoginTicketRecord.class, loginSeq);
	}

	public int invalidLoginRecord(final long loginTicket) {
		return this.getHibernateTemplateEx().executeUpdateBySql(
				"delete from t_login_ticket where login_ticket = ? ",
				loginTicket);
	}

	public int invalidLoginTicketRecord(final Date fromTime) {
		return this.getHibernateTemplateEx().executeUpdateBySql(
				"delete from t_login_ticket where upd_time <= ?", fromTime);
	}

	public int refreshLoginTicketRecord(final long loginSeq, final Date updTime) {
		return this
				.getHibernateTemplateEx()
				.executeUpdateBySql(
						"update t_login_ticket set upd_time = ? where login_ticket = ?",
						updTime, loginSeq);
	}

	public int getLoginTicketRecordSum() {
		Integer result = this.getHibernateTemplate().execute(
				new HibernateCallback<Integer>() {
					public Integer doInHibernate(final Session sess)
							throws HibernateException, SQLException {
						final List<Integer> result = new ArrayList<Integer>(1);
						@SuppressWarnings("deprecation")
						Connection connection = sess.connection(); 
						final String hql = "select count(*) from "
							+ LoginTicketRecord.class.getName();
						int level = connection
								.getTransactionIsolation();
						try {
							connection
									.setTransactionIsolation(Connection.TRANSACTION_READ_UNCOMMITTED);
							Query query = sess.createQuery(hql);
							Object unique = query.uniqueResult();
							Integer count = (unique == null) ? 0
									: Integer.parseInt(unique
											.toString());
							result.add(count);
						} finally {
							connection.setTransactionIsolation(level);
							connection.close();
						}
						return (result.size() == 0) ? 0 : result.get(0);
					}
				});
		return result;
	}

	public int getLoginTicketRecordSum(final String appCode) {
		Integer result = this.getHibernateTemplate().execute(
				new HibernateCallback<Integer>() {
					public Integer doInHibernate(final Session sess)
							throws HibernateException, SQLException {
						final List<Integer> result = new ArrayList<Integer>(1);
						@SuppressWarnings("deprecation")
						Connection connection = sess.connection(); 
						final String hql = "select count(*) from "
								+ LoginTicketRecord.class.getName()
								+ " t where t.appCode=?";
						int level = connection
								.getTransactionIsolation();
						try {
							connection
									.setTransactionIsolation(Connection.TRANSACTION_READ_UNCOMMITTED);
							Query query = sess.createQuery(hql);
							query.setParameter(0, appCode);
							Object unique = query.uniqueResult();
							Integer count = (unique == null) ? 0
									: Integer.parseInt(unique
											.toString());
							result.add(count);
						} finally {
							connection.setTransactionIsolation(level);
							connection.close();
						}
						return (result.size() == 0) ? 0 : result.get(0);
					}
				});
		return result;
	}

}
